package com.vortex.cloud.zhsw.xinyang.util;

import org.apache.commons.lang3.StringUtils;
import org.springframework.util.Assert;
import org.springframework.web.multipart.MultipartFile;

import java.io.*;
import java.nio.charset.Charset;
import java.time.LocalDate;
import java.time.format.DateTimeFormatter;
import java.util.UUID;
import java.util.zip.InflaterInputStream;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;

/**
 * @author huohao@vortexinfo.cn
 * @date 2022/3/15 10:37
 */
public class ZipUtils {
    private static final String TEMPLE_PATH = File.separator + "vortex" + File.separator + "tmp";
    private static int WRITE_SIZE = 8192;
    private static int READ_SIZE = 1024;

    /**
     * 解压文件
     *
     * @param file      文件名称
     * @param unZipPath 解压路径
     * @return java.lang.String 返回解压的文件夹
     * @author huohao@vortexinfo.cn
     */
    public static String unZip(MultipartFile file, String unZipPath) {
        if (StringUtils.isEmpty(unZipPath)) {
            unZipPath = TEMPLE_PATH + File.separator + LocalDate.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd")) + File.separator + UUID.randomUUID();
        }
        try {
            Assert.notNull(file, "文件不能为空");
            ZipInputStream zipInputStream = new ZipInputStream(file.getInputStream(), Charset.forName("GBK"));
            ZipEntry entry = zipInputStream.getNextEntry();
            while (entry != null) {
                if (entry.isDirectory()) {
                    File f = new File(unZipPath + File.separator + entry.getName());
                    if (!f.exists()) {
                        f.mkdirs();
                    }
                } else {
                    // 获取当前条目的字节数组
                    byte[] data = getByte(zipInputStream);
                    Assert.notNull(data, "文件不能为空");
                    InputStream is = new ByteArrayInputStream(data);
                    String[] names = entry.getName().split("/");
                    String path = unZipPath + File.separator;
                    path += join(names, File.separator);
                    File childFile = new File(path);
                    if (!childFile.exists()) {
                        toWrite(is, childFile);
                    }

                }
                entry = zipInputStream.getNextEntry();
            }
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
        return unZipPath;
    }

    /**
     * 向file文件写入字节
     *
     * @param ins  input流
     * @param file 文件
     */
    public static void toWrite(InputStream ins, File file) {
        try {
            OutputStream os = new FileOutputStream(file);
            int bytesRead;
            byte[] buffer = new byte[WRITE_SIZE];
            while ((bytesRead = ins.read(buffer, 0, WRITE_SIZE)) != -1) {
                os.write(buffer, 0, bytesRead);
            }
            os.close();
            ins.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }


    /**
     * /**
     * 获取条目byte[]字节
     *
     * @param zis 压缩文件
     * @return byte[]
     * @author huohao@vortexinfo.cn
     */
    public static byte[] getByte(InflaterInputStream zis) {
        try {
            ByteArrayOutputStream bout = new ByteArrayOutputStream();
            byte[] temp = new byte[READ_SIZE];
            byte[] buf;
            int length;

            while ((length = zis.read(temp, 0, READ_SIZE)) != -1) {
                bout.write(temp, 0, length);
            }

            buf = bout.toByteArray();
            bout.close();
            return buf;
        } catch (IOException e) {
            e.printStackTrace();
            return null;
        }
    }

    public static String join(Object[] o, String flag) {
        StringBuffer strBuff = new StringBuffer();

        for (int i = 0, len = o.length; i < len; i++) {
            strBuff.append(o[i]);
            if (i < len - 1) {
                strBuff.append(flag);
            }
        }

        return strBuff.toString();
    }

}
